using System;
using Microsoft.Xna.Framework;
using SolarWinds.Screens;

namespace SolarWinds.Transitions
{
    public class Transition : GameComponent
    {
        public enum BlendModes
        {
            In,
            Out
        }

        public event EventHandler Started;
        public event EventHandler Ended;

        private TimeSpan mStartTime;
        private bool mInProgress;
        private bool mJustStarted;

        public bool DisposeFlag;

        #region Public Properties

        public BlendModes Mode { get; set; }

        public Screen Screen { get; set; }

        /// <summary>
        /// Duration of the transition.
        /// </summary>
        private TimeSpan mDuration = TimeSpan.FromSeconds(1);

        public TimeSpan Duration
        {
            get { return mDuration; }
            set { mDuration = value; }
        }

        #endregion

        public Transition(Game game)
            : base(game)
        {
        }

        /// <summary>
        /// Starts the transition. 
        /// </summary>
        public void Start()
        {
            mJustStarted = true;
        }

        /// <summary>
        /// Cancels the transition. 
        /// </summary>
        public void Cancel()
        {
            mInProgress = false;
            mJustStarted = false;

            Update(1.0f);

            if (Ended != null)
            {
                Ended(this, null);
            }
        }

        public override void Update(GameTime gameTime)
        {
            TimeSpan currentTime = gameTime.TotalGameTime;

            if (mJustStarted)
            {
                mStartTime = currentTime;
                mInProgress = true;
                mJustStarted = false;

                if (Started != null)
                {
                    Started(this, null);
                }
            }

            var progress = (float)((currentTime.TotalMilliseconds - mStartTime.TotalMilliseconds) / mDuration.TotalMilliseconds);

            if (mInProgress)
            {
                if (progress > 1.0f)
                {
                    progress = 1.0f;
                    mInProgress = false;

                    if (Ended != null)
                    {
                        Ended(this, null);
                    }
                }

                Update(progress);
            }
        }

        protected virtual void Update(float progress)
        {
        }
    }
}